#include "dev_output.h"
#include <string.h>

/**
 * @brief 输出使能
 * @param pstOutput 输出设备
 * @return @see Dev_Ret_t
 */
static Dev_Ret_t
dev_output_active(Dev_Output_t *pstOutput)
{
    // 设置有效状态
    pstOutput->SW.u8State = pstOutput->SW.u8Active;

    // 写入硬件
    pstOutput->HW.pfnWrite(pstOutput->SW.u8State);  
    
    // 返回状态
    return DEV_OK;
}

/**
 * @brief 输出失能
 * @param pstOutput 输出设备
 * @return @see Dev_Ret_t
 */
static Dev_Ret_t
dev_output_inactive(Dev_Output_t *pstOutput)
{
    // 设置无效状态
    pstOutput->SW.u8State = !pstOutput->SW.u8Active;

    // 写入硬件
    pstOutput->HW.pfnWrite(pstOutput->SW.u8State);

    // 返回状态
    return DEV_OK;
}

/**
 * @brief 输出反转
 * @param pstOutput 输出设备
 * @return @see Dev_Ret_t
 */
static Dev_Ret_t
dev_output_toggle(Dev_Output_t *pstOutput)
{
    // 反转状态
    pstOutput->SW.u8State = !pstOutput->SW.u8State;

    // 写入硬件
    pstOutput->HW.pfnWrite(pstOutput->SW.u8State);
    
    // 返回状态
    return DEV_OK;
}

/**
 * @brief 输出设备控制函数
 * @param pstDevice 设备
 * @param u8Cmd 命令
 * @param pvArg 参数
 * @return @see Dev_Ret_t
 */
Dev_Ret_t
dev_output_ioctl(Device_t *pstDevice, uint8_t u8Cmd, void *pvArg)
{
    (void)pvArg;

    // 转换为Dev_Output_t结构体
    Dev_Output_t *pstOutput = GET_CONTEXT(pstDevice, Dev_Output_t);

    // 输入参数检查
    if(NULL == pstOutput->HW.pfnWrite) 
    {
        // 硬件接口为空
        return DEV_INTERFACE_NULL;
    };

    // 执行命令
    switch(u8Cmd)
    {
        case OUTPUT_CMD_ACTIVE:
        {
            // 设置有效状态
            return dev_output_active(pstOutput);
        }

        case OUTPUT_CMD_INACTIVE:
        {
            // 设置无效状态
            return dev_output_inactive(pstOutput);
        }

        case OUTPUT_CMD_TOGGLE:
        {
            // 反转状态
            return dev_output_toggle(pstOutput);
        }
 
        default:
        {
            // 未知命令
            return DEV_UNKNOWN_IOCTL;
        }
    }
}
